﻿using System;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.ServiceModel.Activation;
using System.Collections.Generic;
using System.Data.Objects.DataClasses;
using System.Collections;

namespace SilverlightSdms.Web.Services
{
    [ServiceContract(Namespace = "")]
    [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
    public class VisitsService
    {
        private readonly SdmsEntities _context = new SdmsEntities();

        [OperationContract]
        public List<VisitInfo> GetVisits(int UserId, DateTime Day)
        {
            using (var context = new SdmsEntities())
            {
                return (
                    from visit in context.Visits
                    where visit.User.Id == UserId
                    && visit.StartTime.Month == Day.Month
                    && visit.StartTime.Day == Day.Day
                    select new VisitInfo
                    {
                        VisitId = visit.Id,
                        UserId = visit.User.Id,
                        SchoolName = visit.School.Name,
                        IsDone = visit.IsDone,
                        Description = visit.Description,
                        StartTime = visit.StartTime,
                        EndTime = visit.EndTime
                    }
                    ).ToList<VisitInfo>();
            }
        }

        [OperationContract]
        public List<VisitInfo> GetVisitsForUser(int UserId)
        {
            using (var context = new SdmsEntities())
            {
                return (
                    from visit in context.Visits
                    where visit.User.Id == UserId
                    select new VisitInfo
                    {
                        VisitId = visit.Id,
                        UserId = visit.User.Id,
                        SchoolName = visit.School.Name,
                        IsDone = visit.IsDone,
                        Description = visit.Description,
                        StartTime = visit.StartTime,
                        EndTime = visit.EndTime
                    }
                    ).ToList<VisitInfo>();
            }
        }

        [OperationContract]
        public List<VisitInfo> GetVisitsForTeam(List<int> TeamMembersIDs, int month)
        {
            List<VisitInfo> visitsForTeam = new List<VisitInfo>();

            List<VisitInfo> visits = GetAllVisitsInfo();
            
            foreach (var visit in visits)
	        {
                if (TeamMembersIDs.Contains(visit.UserId) && (month == 13 || visit.StartTime.Month == month))
                {
                    visitsForTeam.Add(visit);
                }
	        }

            return visitsForTeam;
        }

        [OperationContract]
        public List<VisitInfo> GetTeamVisitsForSpecificsSchool(int teamLeaderId, int schoolId)
        {
            List<VisitInfo> visitsForTeamInSchool = new List<VisitInfo>();

            List<User> users = new List<User>();

            var teams = _context.Teams.Where(t => t.TeamLeaderId == teamLeaderId);

            if (teams != null && teams.Count() > 0)
            {
                Team team = teams.First();
                foreach (var item in team.TeamMember)
                {
                    users.Add(item.User);
                }
            }

            foreach (var user in users)
            {
                foreach (var visit in user.Visits)
                {
                    if (visit.School.Id == schoolId)
                    {
                        visitsForTeamInSchool.Add(new VisitInfo
                        {
                            VisitId = visit.Id,
                            UserId = visit.User.Id,
                            SchoolName = visit.School.Name,
                            IsDone = visit.IsDone,
                            Description = visit.Description,
                            StartTime = visit.StartTime,
                            EndTime = visit.EndTime
                        });
                    }
                }
            }

            return visitsForTeamInSchool;
        }

        [OperationContract]
        public List<Visit> GetAllVisits()
        {
            return (from visit in _context.Visits select visit).ToList();
        }

        [OperationContract]
        public List<VisitInfo> GetAllVisitsInfo()
        {
            return (from visit in _context.Visits
                    select new VisitInfo
                    {
                        VisitId = visit.Id,
                        UserId = visit.User.Id,
                        SchoolName = visit.School.Name,
                        IsDone = visit.IsDone,
                        Description = visit.Description,
                        StartTime = visit.StartTime,
                        EndTime = visit.EndTime
                    }).ToList();
        }

        [OperationContract]
        public List<Visit> GetVisitsByDay(DateTime Day, int UserId)
        {
            List<Visit> visits;
            var queryable = from visit in _context.Visits
                            where visit.StartTime.Month == Day.Month
                                    && visit.StartTime.Day == Day.Day
                                    && visit.StartTime.Year == Day.Year
                                    && visit.User.Id == UserId
                            orderby visit.StartTime ascending
                            select visit;
                            
            visits = queryable.ToList();

            return visits;
        }

        [OperationContract]
        public void Update(Visit visit)
        {
            _context.Visits.Attach(visit);
            _context.Visits.ApplyCurrentValues(visit);
            _context.AcceptAllChanges();
            _context.ObjectStateManager.ChangeObjectState(visit, System.Data.EntityState.Modified);
            _context.SaveChanges();
        }

        [OperationContract]
        public void Delete(Visit visit)
        {
            Visit visitToDelete = _context.Visits.First(v => v.Id == visit.Id);
            if (visitToDelete.EntityState == System.Data.EntityState.Detached)
            {
                _context.Visits.Attach(visitToDelete);
            }
            _context.Visits.DeleteObject(visitToDelete);
            _context.SaveChanges();
        }

        [OperationContract]
        public void Add(Visit visit, int UserId, int SchoolId)
        {
            var user = _context.Users.First(u => u.Id == UserId);
            var school = _context.Schools.First(u => u.Id == SchoolId);

            visit.School = school;
            visit.User = user;

            _context.Visits.AddObject(visit);
            _context.SaveChanges();
        }


        [OperationContract]
        public List<ExtendedVisitInfo> GetVisitsForMonth(int UserId, string UserName, int MonthIndex)
        {
            using (var context = new SdmsEntities())
            {
                return (
                    from visit in context.Visits
                    where (visit.User.Id == UserId || visit.User.Name == UserName)
                    && visit.StartTime.Month == MonthIndex
                    select new ExtendedVisitInfo
                    {
                        VisitId = visit.Id,
                        UserId = visit.User.Id,
                        DisplayName = visit.User.DisplayName,
                        SchoolName = visit.School.Name,
                        IsDone = visit.IsDone,
                        Description = visit.Description,
                        StartTime = visit.StartTime,
                        EndTime = visit.EndTime
                    }
                    ).ToList<ExtendedVisitInfo>();
            }                        
        }

        [OperationContract]
        public void AddVisit(DateTime StartTime, double Duration)
        {
            using (var context = new SdmsEntities())
            {
                var user = context.Users.First(u => u.Id == 1);

                var school = context.Schools.First(u => u.Id == 2);
           
                Visit visit = new Visit();
                visit.StartTime = StartTime;
                visit.EndTime = StartTime.AddHours(Duration);
                visit.User = user;
                visit.School = school;
                visit.Description = "Test";
                visit.IsDone = false;
                context.Visits.AddObject(visit);
                context.SaveChanges();
            }
        }

        [OperationContract]
        public void UpdateVisit(VisitInfo VisitInfo)
        {
            using (var context = new SdmsEntities())
            {
                var visit = context.Visits.First(v => v.Id == VisitInfo.VisitId);

                visit.StartTime = VisitInfo.StartTime;
                visit.EndTime = VisitInfo.EndTime;
                visit.School = context.Schools.First(s => s.Name == VisitInfo.SchoolName);
                visit.Description = VisitInfo.Description;
                visit.IsDone = VisitInfo.IsDone;
                context.Visits.ApplyCurrentValues(visit);
                context.ObjectStateManager.ChangeObjectState(visit, System.Data.EntityState.Modified);
                context.SaveChanges();
            }
        }
        // Add more operations here and mark them with [OperationContract]

         
    }

    public class VisitInfo
    {
        public int VisitId { get; set; }
        public int UserId { get; set; }
        public string SchoolName { get; set; }
        public bool IsDone { get; set; }
        public string Description { get; set; }
        public DateTime StartTime { get; set; }
        public DateTime EndTime { get; set; }

        public VisitInfo() { }

        public VisitInfo(int VisitId, int UserId, string SchoolName, bool IsDone, string Description, DateTime StartTiem, DateTime EndTime)
        {
            this.VisitId = VisitId;
            this.UserId = UserId;
            this.SchoolName = SchoolName;
            this.IsDone = IsDone;
            this.Description = Description;
            this.StartTime = StartTime;
            this.EndTime = EndTime;
        }
    }

    public class ExtendedVisitInfo : VisitInfo
    {        
        public string DisplayName {get; set;}        

        public ExtendedVisitInfo() { }

        public ExtendedVisitInfo(int VisitId, int UserId, string DisplayName, string SchoolName, bool IsDone, string Description, DateTime StartTiem, DateTime EndTime)
        {
            this.VisitId = VisitId;
            this.UserId = UserId;
            this.DisplayName = DisplayName;
            this.SchoolName = SchoolName;
            this.IsDone = IsDone;
            this.Description = Description;
            this.StartTime = StartTime;
            this.EndTime = EndTime;
        }
    }
}
